From: Dario Faggioli Date: Fri, 15 Jul 2016 14:49:18 +0000 (+0200) Subject: xen: credit2: prevent load balancing to go mad if time goes backwards X-Git-Tag: archive/raspbian/4.8.0-1+rpi1~1^2~745 X-Git-Url: https://dgit.raspbian.org/%22http:/www.example.com/cgi/%22https:///%22http:/www.example.com/cgi/%22https:/?a=commitdiff_plain;h=11eadabc34625337f7556e9d74f638229f889fd8;p=xen.git xen: credit2: prevent load balancing to go mad if time goes backwards This really should not happen, but: 1. it does happen! Some more info here: http://lists.xen.org/archives/html/xen-devel/2016-06/msg00922.html 2. independently from 1, it makes sense and is easy enough to have a 'safety catch'. The reason why this is particularly bad for Credit2 is that negative values of delta mean out of scale high load (because of the conversion to unsigned). This, for instance in the case of runqueue load, results in a runqueue having its load updated to values of the order of 10000% or so, which in turns means that the load balancer will migrate everything off from the pCPUs in the runqueue, and leave them idle until the load gets back to something sane... which may indeed take a while! This is not a fix for the problem of time going backwards. In fact, if that happens a lot, load tracking accuracy is still compromized, but at least the effect is a lot less bad than before. Signed-off-by: Dario Faggioli Reviewed-by: George Dunlap --- diff --git a/xen/common/sched_credit2.c b/xen/common/sched_credit2.c index 7e572bf2ab..6cb06e8ada 100644 --- a/xen/common/sched_credit2.c +++ b/xen/common/sched_credit2.c @@ -404,6 +404,12 @@ __update_runq_load(const struct scheduler *ops, else { delta = now - rqd->load_last_update; + if ( unlikely(delta < 0) ) + { + d2printk("%s: Time went backwards? now %"PRI_stime" llu %"PRI_stime"\n", + __func__, now, rqd->load_last_update); + delta = 0; + } rqd->avgload = ( ( delta * ( (unsigned long long)rqd->load << prv->load_window_shift ) ) @@ -455,6 +461,12 @@ __update_svc_load(const struct scheduler *ops, else { delta = now - svc->load_last_update; + if ( unlikely(delta < 0) ) + { + d2printk("%s: Time went backwards? now %"PRI_stime" llu %"PRI_stime"\n", + __func__, now, svc->load_last_update); + delta = 0; + } svc->avgload = ( ( delta * ( (unsigned long long)vcpu_load << prv->load_window_shift ) )